package com.csit.dao.impl;

import java.util.Date;
import java.util.Map;

import org.hibernate.Criteria;
import org.hibernate.Query;
import org.hibernate.criterion.CriteriaSpecification;
import org.hibernate.criterion.MatchMode;
import org.hibernate.criterion.Order;
import org.hibernate.criterion.Projections;
import org.hibernate.criterion.Restrictions;
import org.hibernate.transform.Transformers;
import org.springframework.stereotype.Repository;
import org.springframework.util.Assert;

import com.csit.bean.Pager;
import com.csit.dao.BuyDetailDao;
import com.csit.entity.Buy;
import com.csit.entity.BuyDetail;
import com.csit.util.StringUtil;

@Repository
public class BuyDetailDaoImpl extends BaseDaoImpl<BuyDetail, Integer> implements BuyDetailDao {
	
	public Pager queryBuyDetail(Pager pager, Buy buy,Date beginDate,Date endDate) {
		Criteria criteria = getSession().createCriteria(BuyDetail.class);
		criteria.createAlias("buy", "buy", CriteriaSpecification.LEFT_JOIN);
		criteria.createAlias("buy.supplier", "supplierModel", CriteriaSpecification.LEFT_JOIN);
		
		criteria.add(Restrictions.eq("buy.shop", buy.getShop()));
		if(StringUtil.isNotNull(buy.getBuyCode())){
			criteria.add(Restrictions.like("buy.buyCode", buy.getBuyCode(), MatchMode.ANYWHERE));
		}
		if(buy.getSupplier()!=null){
			criteria.add(Restrictions.eq("buy.supplier", buy.getSupplier()));
		}
		if(beginDate!=null){
			criteria.add(Restrictions.ge("buy.buyDate", beginDate));
		}
		if(endDate!=null){
			criteria.add(Restrictions.le("buy.buyDate", endDate));
		}
		
		Long totalCount = (Long) criteria.setProjection(Projections.rowCount()).uniqueResult();

		criteria.setProjection(null);
		criteria.setResultTransformer(CriteriaSpecification.ROOT_ENTITY);
		criteria.setFirstResult(pager.getBeginCount());
		criteria.setMaxResults(pager.getPageSize());
		criteria.addOrder(Order.desc("buy.buyCode")).addOrder(Order.asc("position"));
		pager.setTotalCount(totalCount);
		pager.setList(criteria.list());
		return pager;
	}

	public Integer getMaxPostion(Buy buy) {
		Assert.notNull(buy, "buy is required");
		String hql = "select max(position)+1 from BuyDetail where buy=:buy";
		Query query = getSession().createQuery(hql);
		query.setEntity("buy", buy);
		return (Integer) query.uniqueResult();
	}

	public Pager queryBuyDetail(Pager pager, Buy buy, BuyDetail buyDetail,Date beginDate, Date endDate) {
		Criteria criteria = getSession().createCriteria(BuyDetail.class);
		criteria.createAlias("buy", "buy", CriteriaSpecification.LEFT_JOIN);
		if(buy.getShop()!=null){
			criteria.add(Restrictions.eq("buy.shop", buy.getShop()));
		}
		if(buyDetail.getProduct()!=null){
			criteria.add(Restrictions.eq("product", buyDetail.getProduct()));
		}
		if(beginDate!=null){
			criteria.add(Restrictions.ge("buy.buyDate", beginDate));
		}
		if(endDate!=null){
			criteria.add(Restrictions.le("buy.buyDate", endDate));
		}
		
		Long totalCount = (Long) criteria.setProjection(Projections.rowCount()).uniqueResult();

		criteria.setProjection(null);
		criteria.setResultTransformer(CriteriaSpecification.ROOT_ENTITY);
		criteria.setFirstResult(pager.getBeginCount());
		criteria.setMaxResults(pager.getPageSize());
		criteria.addOrder(Order.desc("buy.buyCode")).addOrder(Order.asc("position"));
		pager.setTotalCount(totalCount);
		pager.setList(criteria.list());
		return pager;
	}

	@SuppressWarnings("unchecked")
	public Map<String, Double> queryTotal(Buy buy, BuyDetail buyDetail,Date beginDate, Date endDate) {
		StringBuilder hql = new StringBuilder("select sum(isnull(a.quantity,0)) as totalQty,sum(isnull(a.amount,0)) as totalAmount from BuyDetail a left join a.buy b where 1=1");
		if(buy.getShop()!=null){
			hql.append(" and b.shop=:shop");
		}
		if(buyDetail.getProduct()!=null){
			hql.append(" and a.product=:product");
		}
		if(beginDate!=null){
			hql.append(" and b.buyDate>=:beginDate");
		}
		if(endDate!=null){
			hql.append(" and b.buyDate<=:endDate");
		}
		Query query = getSession().createQuery(hql.toString());
		
		if(buy.getShop()!=null){
			query.setEntity("shop", buy.getShop());
		}
		if(buyDetail.getProduct()!=null){
			query.setEntity("product", buyDetail.getProduct());
		}
		if(beginDate!=null){
			query.setDate("beginDate", beginDate);
		}
		if(endDate!=null){
			query.setDate("endDate", endDate);
		}
		query.setResultTransformer(Transformers.ALIAS_TO_ENTITY_MAP);
		
		return (Map<String, Double>) query.uniqueResult();
	}

}
